package icu.lingjie.jni;

import icu.lingjie.alone.LingJie;

/**
 * 和 OpenCL 的灵界程序交互
 */
public final class LingJieByCl extends LingJie {

    // 加载 dll
    static {
        try {
            System.loadLibrary("icu_lingjie_jni_LingJieByCl");
        } catch (Throwable e) {
            String libPath = System.getProperty("java.library.path");
            // TODO 如果路径里包含 . 当前目录，就将 dll 拷过去
            if (libPath != null && !libPath.isEmpty()) {
                // 参考 https://blog.csdn.net/weixin_30714077/article/details/114153776
            }
            String msg = "找不到 icu_lingjie_jni_LingJieByCl.dll，请指定 java.library.path, 并把 LingJieByCl.dll 拷过去";
            System.err.println(msg);
            throw new RuntimeException(msg, e);
        }
    }

    // 加速度和距离的关系
    public static final float[] ACCS = new float[64 * 3];
    static {
        for (int i = 0; i < ACCS.length; i++) {
            float r = i;
            r = ((r + 64) / 128);
            ACCS[i] = (1/(r*r*r) - 1/(r*r));
        }
    }


    ////////////////  这几个是 synchronized 的  ///////////////////////

    /**
     * 初始化，加载地图
     * 地图文件的绝对路径，世界的宽高的幂（2的多少次方），加速度数组，OpenCL的一些参数{第几个平台，第几个设备，地图分为多少列，每个工作组多少工作项, 速度的衰减因子(整数代表千分之几) }
     */
    public native synchronized int init(String fileAbsolutePath, int widthPower, int heightPower,float[] acArray, int[] clIntArgs);

    /**
     * 演化，计算下一张地图
     */
    @Override
    public native synchronized int evolution();

    /**
     * 保存地图
     */
    public native synchronized int save();

    /**
     * 保存地图，然后清理资源并关闭
     */
    public native synchronized int close();


    ////////////////  这几个是可以并发调用的  ///////////////////////

    /**
     * 获取一个小格
     */
    @Override
    public native int getPoint(int x, int y);

    /**
     * 对一个小格子施加力
     */
    @Override
    public native int setForce(int x, int y, int fx, int fy);

}
